<template>
  <div class="pulic-model-add">
    <el-breadcrumb separator="/">
      <el-breadcrumb-item>门户管理</el-breadcrumb-item>
      <el-breadcrumb-item
        ><a :href="currentPosition[mode][1]">{{
          currentPosition[mode][0]
        }}</a></el-breadcrumb-item
      >
      <el-breadcrumb-item
        ><a>{{
          currentPosition[mode][$route.query.allInfo ? 3 : 2]
        }}</a></el-breadcrumb-item
      >
    </el-breadcrumb>
    <div class="add-content">
      <div class="add-top">
        <h1>{{ $route.query.allInfo ? "修改" : "新建" }}</h1>
        <div class="buttons">
          <el-button type="primary" @click="submit('publish')">发布</el-button>
          <el-button @click="submit('save')">保存</el-button>
          <el-button @click="$router.back()">取消</el-button>
        </div>
      </div>
      <div class="add-form">
        <el-form
          :model="addForm"
          :rules="rules"
          label-width="100px"
          label-position="right"
          ref="addForm"
        >
          <el-form-item label="标题" prop="title">
            <el-input
              v-model="addForm.title"
              placeholder="标题"
              maxlength="50"
              show-word-limit
            ></el-input>
          </el-form-item>
          <el-form-item
            label="选择分类"
            prop="type_id"
            v-if="mode !== 'rotationChart'"
          >
            <el-select v-model="addForm.type_id">
              <el-option
                v-for="item in classifyOptions"
                :key="item.type_id"
                :label="item.type_name"
                :value="item.type_id"
                >{{ item.type_name }}</el-option
              >
            </el-select>
          </el-form-item>
          <el-form-item label="发布范围" prop="public_range">
            <el-select v-model="addForm.public_range" @change="preRangeChange">
              <el-option
                v-for="item in preRangeOptions"
                :key="item.value"
                :label="item.label"
                :value="item.value"
                >{{ item.label }}</el-option
              >
            </el-select>
          </el-form-item>
          <el-form-item
            v-if="addForm.public_range === 'part'"
            label="配置范围"
            prop="range"
          >
            <el-input v-model="addForm.range" disabled></el-input>
            <tree-search
              @changeDialogVisible="changeDialogVisible"
              @dialogSubmit="dialogSubmit"
              :dialogVisible="dialogVisible"
              :selected_dept="selected_dept"
              :selected_employee="selected_employee"
              mode="all"
            >
              <el-button
                type="text"
                icon="el-icon-plus"
                @click="dialogVisible = true"
                slot="title"
                >添加</el-button
              >
            </tree-search>
          </el-form-item>
          <el-form-item label="来源" prop="from" v-if="mode === 'allNews'">
            <el-input
              v-model="addForm.from"
              maxlength="30"
              show-word-limit
            ></el-input>
          </el-form-item>
          <el-form-item label="有效时间" prop="timeRange">
            <el-date-picker
              v-model="addForm.timeRange[0]"
              type="datetime"
              placeholder="选择日期时间"
              :clearable="false"
            >
            </el-date-picker>
            —
            <el-date-picker
              v-model="addForm.timeRange[1]"
              type="datetime"
              placeholder="选择日期时间"
              :clearable="false"
            >
            </el-date-picker>
            <span style="color: #999"> 结束时间为空需手动终止</span>
          </el-form-item>
          <el-form-item
            label="是否置顶"
            prop="is_top"
            v-if="mode === 'allNews' || mode === 'NoticesManage'"
          >
            <el-radio v-model="addForm.is_top" :label="true">是</el-radio>
            <el-radio v-model="addForm.is_top" :label="false">否</el-radio>
          </el-form-item>
          <el-form-item label="置顶天数" prop="top_day" v-if="addForm.is_top">
            <el-input v-model="addForm.top_day" type="number"></el-input>
          </el-form-item>
          <el-form-item
            label="图片"
            prop="picture"
            v-if="mode === 'rotationChart'"
          >
            <span>支持png、jpeg、jpg、gif格式，5M以内，建议5:3的尺寸</span>
            <el-upload
              class="avatar-uploader"
              :show-file-list="false"
              :on-success="handleAvatarSuccess"
              :before-upload="beforeAvatarUpload"
              action
              :http-request="uploadFile"
              name="upload"
              :on-remove="onRemove"
            >
              <img
                v-if="addForm.picture"
                :src="addForm.picture"
                class="avatar"
              />
              <i v-else class="el-icon-plus avatar-uploader-icon"></i>
            </el-upload>
          </el-form-item>
          <el-form-item
            label="类型"
            prop="data_type"
            v-if="mode !== 'NoticesManage'"
          >
            <el-radio v-model="addForm.data_type" label="article"
              >文章</el-radio
            >
            <el-radio v-model="addForm.data_type" label="out_link"
              >外部链接</el-radio
            >
          </el-form-item>
          <el-form-item
            label="附件"
            prop="appendix"
            v-if="addForm.data_type === 'article'"
          >
            <el-upload
              drag
              action
              :http-request="uploadFile"
              multiple
              class="appendix-content"
              name="upload"
              :on-remove="onRemove"
              :on-preview="onPreview"
              :file-list="showFileList"
            >
              <i class="el-icon-upload"></i>
              <div class="el-upload__text">
                将文件拖到此处，或<em>点击上传</em>
              </div>
              <div class="el-upload__tip" slot="tip">
                支持扩展名：.PDF .PNG .JPG .XLSX .DOC .DOCX .MP4 .ZIP .URL .TXT
                .XLS .JPEG .GIF .PPTX .PPT .ET .PAGES
              </div>
            </el-upload>
          </el-form-item>
          <el-form-item
            label="富文本"
            prop="content"
            v-if="addForm.data_type === 'article'"
          >
            <div style="border: 1px solid #ccc">
              <Toolbar
                style="border-bottom: 1px solid #ccc"
                :editor="richText.editor"
                :defaultConfig="richText.toolbarConfig"
                :mode="richText.mode"
              />
              <Editor
                style="height: 500px; overflow-y: hidden"
                v-model="addForm.content"
                :mode="richText.mode"
                @onCreated="onCreated"
              />
            </div>
          </el-form-item>
          <el-form-item
            label="外部链接"
            prop="outLink"
            v-if="addForm.data_type === 'out_link'"
          >
            <el-input
              v-model="addForm.outLink"
              maxlength="500"
              show-word-limit
            ></el-input>
          </el-form-item>
        </el-form>
      </div>
    </div>
  </div>
</template>

<script>
import tools from "@/utils/tools";
import { Editor, Toolbar } from "@wangeditor/editor-for-vue";
import TreeSearch from "@/components/public/treeSearch.vue";
import {
  addInfoBlock,
  changeInfoBlock,
  getTargetTypes,
  uploadSomething,
} from "@/http/api";
import dayjs from "dayjs";
export default {
  name: "PublicModelAdd",
  components: { Editor, TreeSearch, Toolbar },
  data() {
    return {
      mode: this.$route.query.tab,
      addForm: {
        id: "",
        title: "",
        type_id: "",
        public_range: "",
        range: "",
        from: "",
        timeRange: [tools.formatDate(new Date()), ""],
        is_top: false,
        top_day: 0,
        picture: "",
        appendix: [],
        content: "",
        outLink: "",
        data_type: "article",
      },
      fileList: [],
      showFileList: [],
      appendixMap: {},
      rules: {
        title: [{ required: true, message: "请输入标题" }],
        type_id: [{ required: true, message: "请选择分类" }],
        public_range: [{ required: true, message: "请选择发布范围" }],
        range: [{ required: false, message: "请添加配置范围" }],
        timeRange: [{ required: true }],
        content: [
          {
            required: true,
            message: "请填写内容",
            validator: (_, value, callback) => {
              value = value
                .replace(/<[^<p>]+>/g, "")
                .replace(/<[</p>$]+>/g, "")
                .replace(/&nbsp;/gi, "")
                .replace(/<[^<br/>]+>/g, "");
              if (value == "") callback(new Error("请填写内容"));
              let re = new RegExp("^[ ]+$");
              if (re.test(value)) {
                callback(new Error("请填写内容"));
              } else {
                callback();
              }
            },
          },
        ],
        outLink: [
          {
            required: true,
            message: "请正确填写外链",
            trigger: "blur",
            validator: (_, value, callback) => {
              let res =
                /^(((ht|f)tps?):\/\/)?[\w-]+(.[\w-]+)+([\w.,@?^=%&:/~+#-]*[\w@?^=%&/~+#-])?$/.test(
                  value
                );
              if (res) {
                callback();
              } else {
                callback(new Error());
              }
            },
          },
        ],
        top_day: [{ required: true, message: "请填写置顶天数" }],
        picture: [{ required: true, message: "请上传图片" }],
      },
      classifyOptions: [],
      preRangeOptions: [
        {
          label: "全员可见",
          value: "all",
        },
        {
          label: "指定部门/人员可见",
          value: "part",
        },
      ],
      dialogVisible: false,
      richText: {
        editor: null,
        toolbarConfig: {
          excludeKeys: ["group-image", "group-video"],
        },
        mode: "default",
      },
      currentUrl: "",
      currentPosition: {
        allNews: [
          "新闻管理",
          `${window.location.origin}/#/systemtools/portaladmin/NewsManage?tab=${this.$route.query.tab}`,
          "新建新闻",
          "修改新闻",
        ],
        rotationChart: [
          "新闻管理",
          `${window.location.origin}/#/systemtools/portaladmin/NewsManage?tab=${this.$route.query.tab}`,
          "新建轮播图",
          "修改轮播图",
        ],
        NoticesManage: [
          "通知公告管理",
          `${window.location.origin}/#/systemtools/portaladmin/NoticesManage?tab=${this.$route.query.tab}`,
          "新建通知公告",
          "修改通知公告",
        ],
        RulesManage: [
          "规章制度管理",
          `${window.location.origin}/#/systemtools/portaladmin/RulesManage?tab=${this.$route.query.tab}`,
          "新建规章制度",
          "修改规章制度",
        ],
      },
      selectedRange: "",
      ifConfirm: true,
      selected_dept: [],
      selected_employee: [],
      pictureUrl: "",
    };
  },
  async mounted() {
    this.currentUrl = window.location.href;
    let allInfo = this.$route.query.allInfo;
    if (allInfo) {
      allInfo = JSON.parse(allInfo);
      for (let key in this.addForm) {
        if (key === "range" && allInfo[key]) {
          let res = "";
          let range = allInfo[key];
          res += range.dept.map((item) => item.dept_name).join("、");
          if (range.employee.length) {
            if (res) res += " & ";
            res += range.employee.map((item) => item.employee_name).join(" & ");
          }
          this.addForm[key] = res;
          this.selected_dept = range.dept;
          this.selected_employee = range.employee;
        } else {
          this.addForm[key] =
            allInfo[key] === undefined ? this.addForm[key] : allInfo[key];
        }
      }
      this.addForm.is_top
        ? (this.addForm.is_top = true)
        : (this.addForm.is_top = false);
      this.addForm.outLink =
        this.addForm.data_type === "out_link" ? allInfo.content : "";
      this.addForm.timeRange[0] = dayjs(allInfo.start_time).format(
        "YYYY-MM-DD HH:mm:ss"
      );
      this.addForm.timeRange[1] = allInfo.end_time
        ? dayjs(allInfo.end_time).format("YYYY-MM-DD HH:mm:ss")
        : "";
      if (allInfo.annex_url && allInfo.annex_url.length) {
        this.showFileList = allInfo.annex_url.split(",").map((item) => {
          return { name: item, url: `/local/uploadFiles/${item}` };
        });
        this.fileList = allInfo.annex_url.split(",").map((item) => {
          return { file_name: item, save_code: item };
        });
      }
      if (allInfo.rotation_url) {
        this.addForm.picture = allInfo.rotation_url;
      }
      setTimeout(() => {
        this.addForm.content = allInfo.content;
      });
    }
    this.rules.type_id[0].required = this.mode !== "rotationChart";
    this.rules.picture[0].required = this.mode === "rotationChart";
    let res = {};
    if (this.mode === "allNews") {
      res = await getTargetTypes("NewsManage");
    } else {
      res = await getTargetTypes(this.mode);
    }
    if (res.code === 20041) {
      this.classifyOptions = res.data;
    }
  },
  beforeDestroy() {
    const editor = this.richText.editor;
    if (editor == null) return;
    editor.destroy();
  },
  methods: {
    preRangeChange() {
      this.rules.range[0].required =
        this.addForm.public_range === "part" ? true : false;
    },
    dialogSubmit(selectedNodes) {
      this.selectedRange = selectedNodes;
      let newRange = selectedNodes.dept
        ? selectedNodes.dept.map((item) => item.dept_name).join("、")
        : "";
      this.selectedRange = selectedNodes.dept
        ? selectedNodes.dept.map((item) => item.dept_id).join("、")
        : "";
      if (selectedNodes.employee.length) {
        if (newRange !== "") {
          newRange += " & ";
          this.selectedRange += " & ";
        }
        newRange += selectedNodes.employee
          .map((item) => item.employee_name)
          .join(" & ");
        this.selectedRange += selectedNodes.employee
          .map((item) => item.employee_id)
          .join(" & ");
      }
      this.addForm.range = newRange;
      this.dialogVisible = false;
    },
    onCreated(editor) {
      this.richText.editor = Object.seal(editor);
    },
    submit(type) {
      this.$refs.addForm.validate(async (res) => {
        if (res) {
          this.addForm.appendix = this.fileList;
          let data = { ...this.addForm, info_module_id: this.mode };
          data.annex_url = data.appendix
            .map((item) => item.save_code)
            .join(",");
          data.content =
            data.data_type !== "out_link" ? data.content : data.outLink;
          data.start_time = new Date(data.timeRange[0]);
          data.end_time = data.timeRange[1]
            ? new Date(data.timeRange[1])
            : undefined;
          data.is_top = data.is_top ? 1 : 0;
          data.status = type === "save" ? 0 : -1;
          data.public_range =
            data.public_range === "all" ? "all" : this.selectedRange;
          if (!data.public_range) {
            data.public_range = this.selected_dept
              .map((item) => item.dept_id)
              .join("、");
            if (this.selected_employee.length) {
              if (data.public_range !== "") {
                data.public_range += " & ";
              }
              data.public_range += this.selected_employee
                .map((item) => item.employee_id)
                .join(" & ");
            }
          }
          if (this.mode === "rotationChart") {
            data.rotation_url = this.pictureUrl;
          }
          data.range = undefined;
          if (data.id === "") {
            if (data.public_range === "") {
              data.public_range = "all";
            }
            let res = await addInfoBlock(data);
            if (res.code === 20011) {
              this.$message.success("添加成功");
              this.ifConfirm = false;
              this.$router.back();
            } else {
              this.$message({
                type: "error",
                message: res.msg,
              });
            }
          } else {
            let res = await changeInfoBlock(data);
            if (res.code === 20031) {
              this.$message.success("修改成功");
              this.ifConfirm = false;
              this.$router.back();
            } else {
              this.$message({
                type: "error",
                message: res.msg,
              });
            }
          }
        }
      });
    },
    handleAvatarSuccess(_, file) {
      this.addForm.picture = URL.createObjectURL(file.raw);
      this.pictureUrl =
        "http://localhost/uploadFiles/" +
        this.fileList.filter((item) => item.file_name === file.name)[0]
          .save_code;
      this.fileList = this.fileList.filter(
        (item) => item.file_name !== file.name
      );
    },
    beforeAvatarUpload(file) {
      const isForm =
        file.type === "image/jpeg" ||
        file.type === "image/png" ||
        file.type === "image/gif";
      const isLt5M = file.size / 1024 / 1024 < 5;
      if (!isForm) this.$message.error("请按照格式上传");
      if (!isLt5M) this.$message.error("上传头像图片大小不能超过 2MB!");
      return isForm && isLt5M;
    },
    changeDialogVisible(visible) {
      this.dialogVisible = visible;
    },
    async uploadFile(item) {
      let FormDatas = new FormData();
      FormDatas.append("file", item.file);
      let res = await uploadSomething(FormDatas);
      if (res.code === 20011) {
        this.fileList.push({
          file_name: item.file.name,
          save_code: res.data,
        });
      }
    },
    onRemove(file) {
      this.fileList = this.fileList.filter((item) => {
        return item.file_name !== file.name;
      });
    },
    onPreview(file) {
      if (file.url) {
        window.open(file.url, "_blank");
      } else {
        let fileName = this.fileList.filter(
          (item) => item.file_name === file.name
        )[0].save_code;
        window.open(`http://localhost/uploadFiles/${fileName}`, "_blank");
      }
    },
  },
  watch: {
    "addForm.data_type": {
      handler(newValue) {
        if (newValue === "article") {
          this.rules.content[0].required = true;
          this.rules.outLink[0].required = false;
        } else {
          this.rules.content[0].required = false;
          this.rules.outLink[0].required = true;
        }
      },
      immediate: true,
    },
    "addForm.is_top": {
      handler(newValue) {
        if (newValue === true) {
          this.rules.top_day[0].required = true;
        } else {
          this.rules.top_day[0].required = false;
        }
      },
      immediate: true,
    },
  },
  beforeRouteLeave(to, from, next) {
    if (this.ifConfirm) {
      setTimeout(() => {
        this.$confirm("尚未保存，确定要离开嘛？", "", {
          confirmButtonText: "确定",
          cancelButtonText: "取消",
          type: "warning",
        })
          .then(() => {
            next();
          })
          .catch(() => {
            next(false);
            window.history.replaceState("", "", this.currentUrl);
          });
      });
    } else {
      next();
    }
  },
};
</script>

<style lang="less" scoped>
.pulic-model-add .add-content {
  padding: 24px;
  background-color: #fff;
  .add-top {
    display: flex;
    justify-content: space-between;
    align-items: center;
    margin-bottom: 30px;
    h1 {
      font-weight: 500;
      font-size: 18px;
    }
    .buttons {
      display: flex;
    }
  }
  .add-form {
    width: 75%;
    /deep/ .appendix-content .el-upload {
      width: 100%;
      .el-upload-dragger {
        width: 100%;
      }
    }
    .el-upload__tip {
      position: absolute;
      top: 130px;
      left: 40px;
      color: #999;
    }
    /deep/ div[data-w-e-textarea] {
      height: 300px !important;
    }
    /deep/ input::-webkit-outer-spin-button,
    /deep/ input::-webkit-inner-spin-button {
      -webkit-appearance: none;
    }
    /deep/ .avatar-uploader .el-upload {
      border: 1px solid #d9d9d9;
      border-radius: 6px;
      cursor: pointer;
      position: relative;
      overflow: hidden;
      background-color: #f2f2f2;
    }
    /deep/ .avatar-uploader .el-upload:hover {
      border-color: #409eff;
    }
    .avatar-uploader-icon {
      font-size: 28px;
      color: #8c939d;
      width: 100px;
      height: 100px;
      line-height: 100px;
      text-align: center;
    }
    .avatar {
      width: 100px;
      height: 100px;
      display: block;
    }
  }
}
</style>
<style src="@wangeditor/editor/dist/css/style.css"></style>
